/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package org.rationalsheet.parser.type;

import java.math.BigDecimal;
import java.math.MathContext;
import java.math.RoundingMode;
import java.util.TreeSet;

/**
 *
 * @author Overmind
 */
public class DefaultTypes
{
    private static TreeSet<Type> types;
    
    public static final Type NUMERIC = new TrimType<>(new Type<BigDecimal>("Numeric")
    {
	@Override
	public BigDecimal valueOfString(String string) throws
		NumberFormatException
	{
            return new BigDecimal(string);
	}

        @Override
        public String objectToString(BigDecimal value)
        {
            return value.round(MathContext.DECIMAL32).toString();
        }
    });
    
    public static final Type TEXTUAL = new TrimType<>(new Type<String>("Textual")
    {
	public static final String QUOTE = "\"";
	
	@Override
        public String valueOfString(String string) throws NumberFormatException
        {
	    if((string.length() >= (QUOTE.length()*2)) && 
		    (string.startsWith(QUOTE)) && 
		    (string.endsWith(QUOTE)))
	    {
		return string.substring(QUOTE.length(), string.length() - QUOTE.length());
	    }
	    else
	    {
		throw new NumberFormatException();
	    }
        }

        @Override
        public String objectToString(String value)
        {
            return "\"" + value + "\"";
        }
    });
    
    public static final Type DECIMAL = new TrimType<>(new Type<Integer>("Decimal")
    {
	@Override
        public Integer valueOfString(String string) throws NumberFormatException
        {
            return Integer.parseInt(string);
        }

        @Override
        public String objectToString(Integer value)
        {
            return value.toString();
        }
    });
    
    public static final Type LOGICAL = new TrimType<>(new Type<Boolean>("Logical")
    {
	@Override
        public Boolean valueOfString(String string) throws NumberFormatException
        {
            if(string.equalsIgnoreCase("TRUE"))
	    {
		return true;
	    }
	    else if(string.equalsIgnoreCase("FALSE"))
	    {
		return false;
	    }
	    else
	    {
		throw new NumberFormatException();
	    }
        }

        @Override
        public String objectToString(Boolean value)
        {
            return value.toString().toUpperCase();
        }
    });
    
    public static final Type CUSTOM = new Type<String>("Custom")
    {
	@Override
        public String valueOfString(String string) throws NumberFormatException
        {
            return string;
        }

        @Override
        public String objectToString(String value)
        {
            return value;
        }
    };
    
    private static void init()
    {
	types = new TreeSet<>();
	
	types.add(NUMERIC);
	types.add(TEXTUAL);
	types.add(DECIMAL);
	types.add(LOGICAL);
    }
    
    public static TreeSet<Type> getTypes()
    {
	if(types == null)
	{
	    init();
	}
	
	return types;
    }
}
